package org.lboot.rbac.handler;

import cn.dev33.satoken.exception.NotLoginException;
import cn.dev33.satoken.exception.NotPermissionException;
import cn.dev33.satoken.exception.NotRoleException;
import cn.dev33.satoken.exception.SaTokenException;
import cn.hutool.core.lang.Validator;
import lombok.extern.slf4j.Slf4j;
import org.lboot.core.domain.ErrMsg;
import org.lboot.core.domain.ResponseDTO;
import org.springframework.http.HttpStatus;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.RestControllerAdvice;

/**
 * @author kindear
 * 鉴权系统异常拓展
 */
@Slf4j
@RestControllerAdvice
public class RbacExceptionHandler {
    public String exceptionLocation(Exception ex){
        log.error(ex.getMessage(),ex);
        // 获取异常堆栈跟踪
        StackTraceElement[] stackTrace = ex.getStackTrace();

        if (stackTrace != null && stackTrace.length > 0) {
            // 获取发生异常的类名
            String className = stackTrace[0].getClassName();

            // 获取发生异常的方法名
            String methodName = stackTrace[0].getMethodName();

            // 获取异常发生的行号
            int lineNumber = stackTrace[0].getLineNumber();

            return className+"[" + methodName + "]:" + lineNumber;
        }
        return null;
    }


    @ExceptionHandler({
            NotLoginException.class
    })
    public ResponseDTO<Object> handleUnauthorizedException(SaTokenException ex){
        ErrMsg errMsg = new ErrMsg();
        errMsg.setMessage(ex.getMessage());
        errMsg.setLocation(exceptionLocation(ex));
        errMsg.setHref("http://www.baidu.com");
        if (Validator.isEmpty(errMsg.getStatusCode())){
            errMsg.setStatusCode(401);
        }
        return ResponseDTO.wrap(HttpStatus.UNAUTHORIZED,errMsg);
    }

    @ExceptionHandler({
            NotPermissionException.class,
            NotRoleException.class
    })
    public ResponseDTO<Object> handleForbiddenException(SaTokenException ex){
        ErrMsg errMsg = new ErrMsg();
        errMsg.setMessage(ex.getMessage());
        errMsg.setLocation(exceptionLocation(ex));
        errMsg.setHref("http://www.baidu.com");
        if (Validator.isEmpty(errMsg.getStatusCode())){
            errMsg.setStatusCode(403);
        }
        return ResponseDTO.wrap(HttpStatus.FORBIDDEN,errMsg);
    }
}
